﻿
// oneDlg.cpp: 实现文件
//

#include "stdafx.h"
#include "one.h"
#include "oneDlg.h"
#include "afxdialogex.h"
#include "photo.h"
#include "Login.h"





#define PI 3.1416
#ifdef _DEBUG
#define new DEBUG_NEW
#endif

void callback_demo(int, void*);
void CompImageHist(Mat &src, MatND &b_hist, MatND &g_hist, MatND &r_hist);
double result(Mat img_te, Mat sample);
int rgb2hsi(Mat &, Mat &);
int histogram(Mat&,string names);
int ReadFruit(string names);
double apple_sililar(Mat img) {
	const char* apple_name[] = { "D:\\picture\\apple\\p8.jpg", "D:\\picture\\apple\\hfus.jpg","D:\\picture\\apple\\9_100.jpg","D:\\picture\\apple\\p1.jpg","D:\\picture\\apple\\p5.jpg" };
	double apple_sum = 0;
	double similar_value;
	Mat sample_apple;
	for (int i = 0; i < 5; i++) {
		sample_apple = imread(apple_name[i], -1);
		similar_value = result(img, sample_apple);
		cout << "苹果" << similar_value << endl;
		apple_sum += similar_value;
	}
	double average = apple_sum / 5.0;
	return average;
}
double babana_sililar(Mat img) {
	//const char* apple_name[] = { "D:\\picture\\banana\\bs2.jpg","D:\\picture\\banana\\xj1.jpg","D:\\picture\\banana\\z_banana.png","D:\\picture\\banana\\b2.jpg","D:\\picture\\banana\\b3.jpg" };
	const char* apple_name[] = { "D:\\picture\\banana\\z_banana.png"};
	double apple_sum = 0;
	double similar_value;
	Mat sample_apple;
	for (int i = 0; i < 1; i++) {
		sample_apple = imread(apple_name[i], -1);
		similar_value = result(img, sample_apple);
		cout << "香蕉" << similar_value << endl;
		apple_sum += similar_value;
	}
	double average = apple_sum / 1.0;
	return average;
}
double orange_sililar(Mat img) {
	const char* apple_name[] = { "D:\\picture\\orange\\z_orange.jpg","D:\\picture\\orange\\p16.jpg","D:\\picture\\orange\\p15.jpg","D:\\picture\\orange\\juzi2.jpg","D:\\picture\\orange\\119.jpg"};
	double apple_sum = 0;
	double similar_value;
	Mat sample_apple;
	for (int i = 0; i < 5; i++) {
		sample_apple = imread(apple_name[i], -1);
		similar_value = result(img, sample_apple);
		cout << "橘子" << similar_value << endl;
		apple_sum += similar_value;
	}
	double average = apple_sum / 5.0;
	return average;
}
double averages_apple(Mat img) {
	double average_apple = apple_sililar(img);
	return average_apple;
}
double averages_banana(Mat img) {
	double average_banana = babana_sililar(img);
	return average_banana;
}
double averages_orange(Mat img) {
	double average_orange = orange_sililar(img);
	return average_orange;
}






// 用于应用程序“关于”菜单项的 CAboutDlg 对话框

//全局变量
Mat image_all;

class CAboutDlg : public CDialogEx
{
public:
	CAboutDlg();
	CFont m_oFont;

// 对话框数据
#ifdef AFX_DESIGN_TIME
	enum { IDD = IDD_ABOUTBOX };
#endif

	protected:
	virtual void DoDataExchange(CDataExchange* pDX);    // DDX/DDV 支持

// 实现
protected:
	DECLARE_MESSAGE_MAP()
};

CAboutDlg::CAboutDlg() : CDialogEx(IDD_ABOUTBOX)
{
}

void CAboutDlg::DoDataExchange(CDataExchange* pDX)
{
	CDialogEx::DoDataExchange(pDX);
}

BEGIN_MESSAGE_MAP(CAboutDlg, CDialogEx)
END_MESSAGE_MAP()


// ConeDlg 对话框



ConeDlg::ConeDlg(CWnd* pParent /*=nullptr*/)
	: CDialogEx(IDD_ONE_DIALOG, pParent)
{
	m_hIcon = AfxGetApp()->LoadIcon(IDR_MAINFRAME);
}

void ConeDlg::DoDataExchange(CDataExchange* pDX)
{
	CDialogEx::DoDataExchange(pDX);
	DDX_Control(pDX, kind002, m_edit);
}

BEGIN_MESSAGE_MAP(ConeDlg, CDialogEx)
	ON_WM_SYSCOMMAND()
	ON_WM_PAINT()
	ON_WM_QUERYDRAGICON()
	ON_BN_CLICKED(IDC_BUTTON1, &ConeDlg::OnBnClickedButton1)
	ON_BN_CLICKED(IDC_BUTTON2, &ConeDlg::OnBnClickedButton2)
//	ON_BN_CLICKED(IDOK, &ConeDlg::OnBnClickedOk)
	ON_BN_CLICKED(IDC_BUTTON5, &ConeDlg::OnBnClickedButton5)
	ON_BN_CLICKED(IDC_BUTTON6, &ConeDlg::OnBnClickedButton6)
	ON_EN_CHANGE(text3, &ConeDlg::OnEnChangetext3)
//	ON_BN_CLICKED(IDC_BUTFRUIT, &ConeDlg::OnBnClickedButfruit)
	ON_BN_CLICKED(IDC_BUTFRUITT, &ConeDlg::OnBnClickedButfruitt)
	ON_BN_CLICKED(butten004, &ConeDlg::OnBnClickedbutten004)
	ON_WM_CTLCOLOR()
	ON_WM_SIZE()
	ON_BN_CLICKED(IDC_BUTTON44, &ConeDlg::OnBnClickedButton44)
	ON_EN_CHANGE(kind002, &ConeDlg::OnEnChangekind002)
END_MESSAGE_MAP()


// ConeDlg 消息处理程序

BOOL ConeDlg::OnInitDialog()
{
	CDialogEx::OnInitDialog();

	Login myDly;
	myDly.DoModal();


	m_oFont.CreatePointFont(180, _T("隶书"));
	m_edit.SetFont(&m_oFont);


	// 将“关于...”菜单项添加到系统菜单中。
	CRect rect;
	GetClientRect(&rect); //取客户区大小   
	Old.x = rect.right - rect.left;
	Old.y = rect.bottom - rect.top;



	CBitmap bmp;
	bmp.LoadBitmap(IDB_BITMAP1);   //IDB_BITMAP1是图片资源ID
	m_brush.CreatePatternBrush(&bmp);


	// IDM_ABOUTBOX 必须在系统命令范围内。
	ASSERT((IDM_ABOUTBOX & 0xFFF0) == IDM_ABOUTBOX);
	ASSERT(IDM_ABOUTBOX < 0xF000);

	CMenu* pSysMenu = GetSystemMenu(FALSE);
	if (pSysMenu != nullptr)
	{
		BOOL bNameValid;
		CString strAboutMenu;
		bNameValid = strAboutMenu.LoadString(IDS_ABOUTBOX);
		ASSERT(bNameValid);
		if (!strAboutMenu.IsEmpty())
		{
			pSysMenu->AppendMenu(MF_SEPARATOR);
			pSysMenu->AppendMenu(MF_STRING, IDM_ABOUTBOX, strAboutMenu);
		}
	}

	// 设置此对话框的图标。  当应用程序主窗口不是对话框时，框架将自动
	//  执行此操作
	SetIcon(m_hIcon, TRUE);			// 设置大图标
	SetIcon(m_hIcon, FALSE);		// 设置小图标

	// TODO: 在此添加额外的初始化代码
	/*namedWindow("view", WINDOW_AUTOSIZE);
	HWND hWnd = (HWND)cvGetWindowHandle("view");
	HWND hParent = ::GetParent(hWnd);
	::SetParent(hWnd, GetDlgItem(IDC_STATIC)->m_hWnd);
	::ShowWindow(hParent, SW_HIDE);*/




	namedWindow("view", WINDOW_AUTOSIZE);
	HWND hWnd = (HWND)cvGetWindowHandle("view");
	HWND hParent = ::GetParent(hWnd);
	::SetParent(hWnd, GetDlgItem(IDC_STATIC)->m_hWnd);
	::ShowWindow(hParent, SW_HIDE);

	

	namedWindow("view9", WINDOW_AUTOSIZE);
	HWND hWnd9 = (HWND)cvGetWindowHandle("view9");
	HWND hParent9 = ::GetParent(hWnd9);
	::SetParent(hWnd9, GetDlgItem(IDC_STATIC9)->m_hWnd);
	::ShowWindow(hParent9, SW_HIDE);




	return TRUE;  // 除非将焦点设置到控件，否则返回 TRUE
}

void ConeDlg::OnSysCommand(UINT nID, LPARAM lParam)
{
	if ((nID & 0xFFF0) == IDM_ABOUTBOX)
	{
		CAboutDlg dlgAbout;
		dlgAbout.DoModal();
	}
	else
	{
		CDialogEx::OnSysCommand(nID, lParam);
	}
}

// 如果向对话框添加最小化按钮，则需要下面的代码
//  来绘制该图标。  对于使用文档/视图模型的 MFC 应用程序，
//  这将由框架自动完成。

void ConeDlg::OnPaint()
{
	if (IsIconic())
	{
		CPaintDC dc(this); // 用于绘制的设备上下文
		SendMessage(WM_ICONERASEBKGND, reinterpret_cast<WPARAM>(dc.GetSafeHdc()), 0);
		// 使图标在工作区矩形中居中
		int cxIcon = GetSystemMetrics(SM_CXICON);
		int cyIcon = GetSystemMetrics(SM_CYICON);
		CRect rect;
		GetClientRect(&rect);
		int x = (rect.Width() - cxIcon + 1) / 2;
		int y = (rect.Height() - cyIcon + 1) / 2;

		// 绘制图标
		dc.DrawIcon(x, y, m_hIcon);
	}
	else
	{
		CDialogEx::OnPaint();
	}
}

//当用户拖动最小化窗口时系统调用此函数取得光标
//显示。
HCURSOR ConeDlg::OnQueryDragIcon()
{
	return static_cast<HCURSOR>(m_hIcon);
}


int element_size = 1, max_size = 20;
Mat imagedst;
void ConeDlg::OnBnClickedButton1()
{
	// TODO: 在此添加控件通知处理程序代码
	//CString picPath("C:\\Users\\Administrator\\Desktop\\图片\\1.jpg");   //定义图片路径变量  
	CString picPath;  //定义图片路径变量  
	CFileDialog dlg(TRUE, NULL, NULL, OFN_HIDEREADONLY |
		OFN_OVERWRITEPROMPT | OFN_ALLOWMULTISELECT, NULL, this);  //选择文件对话框  
	if (dlg.DoModal() == IDOK)
	{
		picPath = dlg.GetPathName();  //获取图片路径  
	}
	//CString to string  使用这个方法记得字符集选用“使用多字节字符”，不然会报错  
	string picpath = CT2A(picPath.GetBuffer());
	//string picpath = "C:\\Users\\Administrator\\Desktop\\图片\\1.jpg";
	Mat image = imread(picpath);
	
	

	//以下操作获取图形控件尺寸并以此改变图片尺寸  
	CRect rect;
	GetDlgItem(IDC_STATIC)->GetClientRect(&rect);
	Rect dstf(rect.left, rect.top, rect.right, rect.bottom);
	resize(image, imagedst, cv::Size(rect.Width(), rect.Height()));
	imshow("view", imagedst);
	



	Mat mid, dst, dsst, gray,src;//mat类型的中间变量和目标图像
	src = image;
	mid = src.clone();
	dst = src.clone();//原图像深拷贝到目标图像
	dsst = src.clone();
	GaussianBlur(dst, dst, Size(9, 9), 2, 2); //高斯滤波
	medianBlur(dst, dst, 5);
	//cvtColor(dst, mid, COLOR_BGR2GRAY); //转化为灰度图像
	Canny(dst, gray, 1, 100);

	//imshow(" ", gray);
	//

//进行霍夫圆变换
	vector<Vec3f>circles;
	HoughCircles(gray, circles, HOUGH_GRADIENT, 1.6, 30, 100, 70, 0, 40);
	//依次在图中绘制出圆
	int ss = 1;
	for (size_t i = 0; i < circles.size(); i++)
	{
		//找出圆心和半径
		Point center(cvRound(circles[i][0]), cvRound(circles[i][1]));
		int radius = cvRound(circles[i][2]);
		//绘制圆心和半径
		//circle(src, center, 3, Scalar(0, 255, 0), -1, 8, 0);
		//circle(src, center, radius, Scalar(155, 50, 255), 1, 8, 0);
		Mat p;
		Rect rect(cvRound(circles[i][0]) - radius, cvRound(circles[i][1]) - radius, radius * 2, radius * 2);
		Point x1y1(cvRound(circles[i][0]) - radius, cvRound(circles[i][1]) + radius);
		Point x2y2(cvRound(circles[i][0]) + radius, cvRound(circles[i][1]) - radius);
		rectangle(src, x1y1, x2y2, Scalar(255, 0, 0), 2, LINE_8, 0);
		mid(rect).copyTo(p);
		long double sumr = 0, sumg = 0, sumb = 0;
		for (int i = 0; i < p.rows; i++)
		{
			for (int j = 0; j < p.cols; j++)
			{
				sumb += (float)p.at<Vec3b>(i, j)[0];
				sumg += (float)p.at<Vec3b>(i, j)[1];
				sumr += (float)p.at<Vec3b>(i, j)[2];
			}
		}
		double numr = sumr / (p.rows*p.cols);
		double numg = sumg / (p.rows*p.cols);
		double numb = sumb / (p.rows*p.cols);
		//cout << "(" << numr << "," << numg << "," << numb << ")" << endl;
		if (numr > 130 && numg < 130 && numb < 130) {
			//waitKey(50);
			char filename[60];
			sprintf_s(filename, "D:\\picture\\p%d.jpg", ss);
			imwrite(filename, p);
			ss++;
		}
		else if (numr >= 120 && numg <= 180 && numg >= 100 && numb <= 100) {
			char filename[60];
			sprintf_s(filename, "D:\\picture\\p%d.jpg", ss);
			imwrite(filename, p);
			ss++;
		}
		
	}


}


void ConeDlg::OnNMCustomdrawSlider1(NMHDR *pNMHDR, LRESULT *pResult)
{
	LPNMCUSTOMDRAW pNMCD = reinterpret_cast<LPNMCUSTOMDRAW>(pNMHDR);
	// TODO: 在此添加控件通知处理程序代码
	*pResult = 0;
	//cout << *pResult<<"\n";
}


void ConeDlg::OnBnClickedButton2()
{

	for (int i = 0; i < 8; i++)
	{
		int aa = i+1;
		stringstream ss;
		ss << aa;
		string s1 = ss.str();
		// TODO: 在此添加控件通知处理程序代码
		string str_pic="picture\\p" + s1+ ".jpg";
		Mat new_img = imread(str_pic);
		Mat dst;

		

		//ss = IDC_STATIC;
		CRect rect;
		GetDlgItem(IDC_STATIC1)->GetClientRect(&rect);
		Rect dstf(rect.left, rect.top, rect.right, rect.bottom);
		resize(new_img, new_img, cv::Size(rect.Width(), rect.Height()));
		//imshow("view", imagedst);


		string name = "view" + s1;
		imshow(name, new_img);
	}
	
}





void ConeDlg::OnBnClickedButton5()
{
	//ConeDlg::OnInitDialog();
	CDialogEx::OnCancel();

	//// TODO: 在此添加控件通知处理程序代码
	//CString str;
	//GetDlgItemText(text3,str);
	//double n_kilo = atof(str);
	//if (n_kilo!=0)
	//{
	//	MessageBox(TEXT("苹果5元一千克\n橘子3元一千克"), TEXT("温馨提示"), MB_OK);


	//	//输入测试图片
	//	//Mat img = imread("F:\\人工007\\仓库\\xixi\\xixi\\classall\\one\\picture\\p13.jpg", -1);
	//	Mat sample_banana, sample_apple, sample_tangerine;
	//	//香蕉模板
	//	sample_banana = imread("F:\\人工007\\仓库\\xixi\\xixi\\classall\\one\\picture\\z_banana.png", -1);
	//	//苹果模板
	//	sample_apple = imread("F:\\人工007\\仓库\\xixi\\xixi\\classall\\one\\picture\\z_Apale.jpg", -1);
	//	//橘子模板
	//	sample_tangerine = imread("F:\\人工007\\仓库\\xixi\\xixi\\classall\\one\\picture\\z_orange.jpg", -1);
	//	double similar[3], temp;
	//	similar[0] = result(image_all, sample_banana);
	//	similar[1] = result(image_all, sample_apple);
	//	similar[2] = result(image_all, sample_tangerine);
	//	double similar_temp[3] = { similar[0],similar[1],similar[2] };
	//	//for (int i = 0; i < 3; i++)
	//	//{
	//	//	// 比较直方图
	//	//	//printf("各通道比较结果... \n\n");
	//	//	//cout << similar[i]<<endl;
	//	//}
	//	for (int i = 0; i < 2; i++) {

	//		for (int j = 0; j < 2; j++) {
	//			if (similar[j] > similar[j + 1]) {
	//				temp = similar[j];
	//				similar[j] = similar[j + 1];
	//				similar[j + 1] = temp;
	//			}
	//		}
	//	}
	//	string name_kind;
	//	const char* names[] = { "香蕉","苹果","橘子" };
	//	for (int j = 0; j < 3; j++) {
	//		if (similar[2] == similar_temp[j]) {
	//			name_kind = names[j];
	//			//cout << names[j] << endl;
	//			//cout << similar[2] << endl;
	//		}
	//	}

	//	if (name_kind=="苹果")
	//	{
	//		double b_value = n_kilo * 5.0;
	//		CString strMsg;
	//		strMsg.Format("种类：苹果\n单价：5元/千克\n需要支付：%lf", b_value);
	//		//MessageBox(TEXT("种类：香蕉\n单价：5元/千克\n需要支付："+s1), TEXT("是否进行购买"), MB_YESNO);
	//		MessageBoxEx(this->m_hWnd, strMsg, TEXT("是否进行购买"), MB_OK, MAKELANGID(LANG_CHINESE_SIMPLIFIED, SUBLANG_CHINESE_TRADITIONAL));
	//	}
	//	else if(name_kind == "橘子")
	//	{
	//		double b_value = n_kilo * 3.0;
	//		CString strMsg;
	//		strMsg.Format("种类：橘子\n单价：3元/千克\n需要支付：%lf", b_value);
	//		//MessageBox(TEXT("种类：香蕉\n单价：5元/千克\n需要支付："+s1), TEXT("是否进行购买"), MB_YESNO);
	//		MessageBoxEx(this->m_hWnd, strMsg, TEXT("是否进行购买"), MB_OK, MAKELANGID(LANG_CHINESE_SIMPLIFIED, SUBLANG_CHINESE_TRADITIONAL));
	//	}
	//	else if(name_kind == "香蕉")
	//	{
	//		double b_value = n_kilo * 2.0;
	//		CString strMsg;
	//		strMsg.Format("种类：香蕉\n单价：2元/千克\n需要支付：%lf", b_value);
	//		//MessageBox(TEXT("种类：香蕉\n单价：5元/千克\n需要支付："+s1), TEXT("是否进行购买"), MB_YESNO);
	//		MessageBoxEx(this->m_hWnd, strMsg, TEXT("是否进行购买"), MB_OK, MAKELANGID(LANG_CHINESE_SIMPLIFIED, SUBLANG_CHINESE_TRADITIONAL));
	//	}
	//	

	//	
	//}
	//else
	//{
	//	MessageBoxEx(this->m_hWnd,"请先输入购买的重量", TEXT("温馨提示"), MB_OK, MAKELANGID(LANG_CHINESE_SIMPLIFIED, SUBLANG_CHINESE_TRADITIONAL));
	//}
	
}


void ConeDlg::OnBnClickedButton6()
{
	// TODO: 在此添加控件通知处理程序代码
	CString str;
	GetDlgItemText(kind002, str);
	string f_name = CT2A(str.GetBuffer());

	int num_value=ReadFruit(f_name);

	if (num_value==1)
	{
		MessageBox(TEXT("该水果已成熟"), TEXT("温馨提示"), MB_OK);
	}
	else if(num_value == 0)
	{
		MessageBox(TEXT("该水果没成熟"), TEXT("温馨提示"), MB_OK);
	}
	else if(num_value == 2)
	{
		MessageBox(TEXT("半熟"), TEXT("温馨提示"), MB_OK);
	}
	else if(num_value == 3)
	{
		MessageBox(TEXT("过熟"), TEXT("温馨提示"), MB_OK);
	}
}

void ConeDlg::OnEnChangetext3()
{
	// TODO:  如果该控件是 RICHEDIT 控件，它将不
	// 发送此通知，除非重写 CDialogEx::OnInitDialog()
	// 函数并调用 CRichEditCtrl().SetEventMask()，
	// 同时将 ENM_CHANGE 标志“或”运算到掩码中。

	// TODO:  在此添加控件通知处理程序代码

	//MessageBox(TEXT("苹果2.5一斤\n橘子1.5一斤"), TEXT("新建任务"), MB_YESNO);
}




void ConeDlg::OnBnClickedButfruitt()
{
	// TODO: 在此添加控件通知处理程序代码
	CString picPath;   //定义图片路径变量  
	CFileDialog dlg(TRUE, NULL, NULL, OFN_HIDEREADONLY |
		OFN_OVERWRITEPROMPT | OFN_ALLOWMULTISELECT, NULL, this);  //选择文件对话框  
	if (dlg.DoModal() == IDOK)
	{
		picPath = dlg.GetPathName();  //获取图片路径  
	}
	//CString to string  使用这个方法记得字符集选用“使用多字节字符”，不然会报错  
	string picpath = CT2A(picPath.GetBuffer());
	//string picpath = "C:\\Users\\Administrator\\Desktop\\图片\\1.jpg";
	image_all = imread(picpath);



	//以下操作获取图形控件尺寸并以此改变图片尺寸  
	CRect rect;
	GetDlgItem(IDC_STATIC9)->GetClientRect(&rect);
	Rect dstf(rect.left, rect.top, rect.right, rect.bottom);
	resize(image_all, imagedst, cv::Size(rect.Width(), rect.Height()));

	imshow("view9", imagedst);





}

void ConeDlg::OnBnClickedbutten004()
{
	//// TODO: 在此添加控件通知处理程序代码
	////输入测试图片
	//	//Mat img = imread("F:\\人工007\\仓库\\xixi\\xixi\\classall\\one\\picture\\p13.jpg", -1);

	//Mat sample_banana, sample_apple, sample_tangerine;
	////香蕉模板
	//sample_banana = imread("D:\\picture\\z_banana.png", -1);
	////苹果模板
	//sample_apple = imread("D:\\picture\\z_Apale.jpg", -1);
	////橘子模板
	//sample_tangerine = imread("D:\\picture\\z_orange.jpg", -1);
	//double similar[3], temp;
	//similar[0] = result(image_all, sample_banana);
	//similar[1] = result(image_all, sample_apple);
	//similar[2] = result(image_all, sample_tangerine);
	//double similar_temp[3] = { similar[0],similar[1],similar[2] };



	const char* names[] = { "苹果","香蕉","橘子" };
	double similar[3], temp;
	similar[0] = averages_apple(image_all);
	similar[1] = averages_banana(image_all);
	similar[2] = averages_orange(image_all);
	double similar_temp[3] = { similar[0],similar[1],similar[2] };
	//for (int i = 0; i < 3; i++)
	//{
	//	// 比较直方图
	//	//printf("各通道比较结果... \n\n");
	//	//cout << similar[i]<<endl;
	//}
	for (int i = 0; i < 2; i++) {

		for (int j = 0; j < 2; j++) {
			if (similar[j] > similar[j + 1]) {
				temp = similar[j];
				similar[j] = similar[j + 1];
				similar[j + 1] = temp;
			}
		}
	}
	string name_kind;
	//const char* names[] = { "香蕉","苹果","橘子" };
	for (int j = 0; j < 3; j++) {
		if (similar[2] == similar_temp[j]) {
			name_kind = names[j];
			//cout << names[j] << endl;
			//cout << similar[2] << endl;
		}
	}


	CString strMsg;
	if (name_kind=="苹果")
	{
		strMsg.Format("苹果");
	}
	else if (name_kind == "橘子")
	{
		strMsg.Format("橘子");
	}
	else
	{
		strMsg.Format("香蕉");
	}
	
	/*m_oFont.CreatePointFont(180, strMsg);

	m_edit.SetFont(&m_oFont);*/


	SetDlgItemText(kind002, strMsg);


}










// 计算图像直方图
void CompImageHist(Mat &src, MatND &b_hist, MatND &g_hist, MatND &r_hist)
{
	// 分割成3个单通道图像(bgr)
	vector<Mat> rgb_planes;
	split(src, rgb_planes);

	// 设定bin数目及取值范围
	int histSize = 255;
	float range[] = { 0, 255 };
	const float* histRange = { range };

	// 计算直方图
	bool uniform = true;
	bool accumulate = false;
	calcHist(&rgb_planes[0], 1, 0, Mat(), b_hist, 1, &histSize, &histRange, uniform, accumulate);
	calcHist(&rgb_planes[1], 1, 0, Mat(), g_hist, 1, &histSize, &histRange, uniform, accumulate);
	calcHist(&rgb_planes[2], 1, 0, Mat(), r_hist, 1, &histSize, &histRange, uniform, accumulate);

	// 直方图归一化>>范围为[0, 1]
	normalize(r_hist, r_hist, 0, 1, NORM_MINMAX, -1/*, Mat()*/);
	normalize(g_hist, g_hist, 0, 1, NORM_MINMAX, -1/*, Mat()*/);
	normalize(b_hist, b_hist, 0, 1, NORM_MINMAX, -1/*, Mat()*/);
}
double result(Mat img_te, Mat sample) {
	Mat img0 = img_te;
	//imshow("img0", img0);
	Mat img1 = sample;
	MatND hist0[3], hist1[3];
	// 计算图像直方图
	CompImageHist(img0, hist0[0], hist0[1], hist0[2]);
	CompImageHist(img1, hist1[0], hist1[1], hist1[2]);

	double sum[4] = { 0.0 };
	double results[4] = { 0.0 };
	char channelName[][8] = { { "蓝色" }, { "绿色" }, { "红色" } };

	for (int i = 0; i < 3; i++)
	{
		// 相关: CV_COMP_CORREL,卡方: CV_COMP_CHISQR,相交: CV_COMP_INTERSECT,巴氏: CV_COMP_BHATTACHARYYA
		results[0] = compareHist(hist0[i], hist1[i], HISTCMP_CORREL);
		results[1] = compareHist(hist0[i], hist1[i], HISTCMP_CHISQR);
		results[2] = compareHist(hist0[i], hist1[i], HISTCMP_INTERSECT);
		results[3] = compareHist(hist0[i], hist1[i], HISTCMP_BHATTACHARYYA);
		sum[0] += results[0];
		sum[1] += results[1];
		sum[2] += results[2];
		sum[3] += results[3];
		//printf("%s-->相关: %f, 卡方: %f, 相交: %f, 巴氏: %f \n", channelName[i], results[0], results[1], results[2], results[3]);
	}
	//printf("\n均值-->相关: %f, 卡方: %f, 相交: %f, 巴氏: %f \n", sum[0] / 3, sum[1] / 3, sum[2] / 3, sum[3] / 3);
	//cout << sum[0] / 3 << endl;
	return sum[0] / 3;
}



//空间转换
int rgb2hsi(Mat &image, Mat &hsi)
{
	if (!image.data) {
		cout << "Miss Data" << endl;
		return -1;
	}
	int nl = image.rows;
	int nc = image.cols;
	if (image.isContinuous()) {
		nc = nc * nl;
		nl = 1;
	}
	for (int i = 0; i < nl; i++) {
		uchar *src = image.ptr<uchar>(i);
		uchar *dst = hsi.ptr<uchar>(i);
		for (int j = 0; j < nc; j++) {
			float b = src[j * 3] / 255.0;
			float g = src[j * 3 + 1] / 255.0;
			float r = src[j * 3 + 2] / 255.0;
			float num = (float)(0.5*((r - g) + (r - b)));
			float den = (float)sqrt((r - g)*(r - g) + (r - b)*(g - b));
			float H, S, I;
			//分母不能为0
			if (den == 0)

				H = 0;

			else {
				double theta = acos(num / den);
				if (b <= g)
					H = theta / (PI * 2);
				else
					H = (2 * PI - theta) / (2 * PI);
			}
			double minRGB = min(min(r, g), b);
			den = r + g + b;
			//分母不能为0
			if (den == 0) {
				S = 0;
			}
			else
				S = 1 - 3 * minRGB / den;
			I = den / 3.0;
			//将S分量和H分量都扩充到[0,255]区间以便于显示;
			//一般H分量在[0,2pi]之间，S在[0,1]之间
			dst[3 * j] = H * 255;
			dst[3 * j + 1] = S * 255;
			dst[3 * j + 2] = I * 255;
		}
	}
	return 0;
}

//直方图
int histogram(Mat& image,string names)
{
	//分通道显示
	vector<Mat> bgr_planes;
	split(image, bgr_planes);

	//计算直方图
	int histSize = 256;
	float range[] = { 0,256 };
	const float *histRanges = { range };
	Mat b_hist, g_hist, r_hist;
	calcHist(&bgr_planes[0], 1, 0, Mat(), b_hist, 1, &histSize, &histRanges, true, false);
	calcHist(&bgr_planes[1], 1, 0, Mat(), g_hist, 1, &histSize, &histRanges, true, false);
	calcHist(&bgr_planes[2], 1, 0, Mat(), r_hist, 1, &histSize, &histRanges, true, false);
	//归一化
	int hist_h = 400;
	int hist_w = 512;
	int bin_w = hist_w / histSize;
	Mat histImage(hist_w, hist_h, CV_8UC3, Scalar(0, 0, 0));
	normalize(b_hist, b_hist, 0, hist_h, NORM_MINMAX, -1, Mat());
	normalize(g_hist, g_hist, 0, hist_h, NORM_MINMAX, -1, Mat());
	normalize(r_hist, r_hist, 0, hist_h, NORM_MINMAX, -1, Mat());
	int sumAll = 0;
	//char names[5];

	for (int i = 1; i < histSize; i++)
	{
		line(histImage, Point((i - 1)*bin_w, hist_h - cvRound(b_hist.at<float>(i - 1))),
			Point((i)*bin_w, hist_h - cvRound(b_hist.at<float>(i))), Scalar(255, 0, 0), 2, LINE_AA);//B通道
		if (names == "苹果")
		{
			if (i < 50)
			{
				sumAll += cvRound(b_hist.at<float>(i - 1));
			}
		}
		else if (names == "橘子")
		{
			if (i < 42)
			{
				sumAll += cvRound(b_hist.at<float>(i - 1));
			}
		}
		else if (names == "香蕉")
		{
			if (i < 42)
			{
				sumAll += cvRound(b_hist.at<float>(i - 1));
			}
		}

	}



	if (names == "苹果")
	{
		if (sumAll > 1500 && sumAll < 3500)
		{
			cout << "苹果半成熟" << endl;
			return 2;

		}
		else if (sumAll > 860 && sumAll < 1500 || sumAll < 650)
		{
			cout << "苹果过熟" << endl;
			return 3;
		}
		else if (sumAll > 650 && sumAll < 860)
		{
			cout << "苹果成熟" << endl;
			return 1;
		}
		else
		{
			cout << "苹果未熟" << endl;
			return 0;
		}

	}

	else if (names == "橘子")
	{
		cout << sumAll << endl;
		if (sumAll > 1000)
		{
			cout << "橘子成熟" << endl;
			return 1;
		}
		else
		{
			cout << "橘子未成熟" << endl;
			return 0;
		}
	}
	else if (names == "香蕉")
	{
		cout << sumAll << endl;
		if (sumAll > 1000)
		{
			cout << "香蕉成熟" << endl;
			return 1;
		}
		else
		{
			cout << "香蕉未成熟" << endl;
			return 0;
		}
	}

	char string[100];
	Size text_size;
	double font_size = 1;//字体大小
	int horvizon_scale = 3;	//水平缩放比
	int shift_horvizon = 10;	//直方图偏移值,偏移用于显示垂直坐标
	int bin = 255;//直方图横坐标的区间数 即横坐标被分成多少份
	float hranges[2] = { 1, 255 };	//直方图统计的灰度值范围
	//刻画水平刻度
	for (int i = bin; i >= 0;)
	{
		_itoa_s(i, string, 10);//把一个整数转换为字符串  
		//在图像中显示文本字符串  
		text_size = getTextSize(string, CV_FONT_HERSHEY_PLAIN, font_size, 1, NULL);	//获得字体大小
		putText(histImage, string, cvPoint(i*horvizon_scale + shift_horvizon - text_size.width / 2, histImage.rows), cv::FONT_HERSHEY_PLAIN, font_size, Scalar(0, 0, 255), 1, 8, 0);
		i -= bin / 20;	//只显示20个刻度
	}
	//显示统计信息
	sprintf_s(string, "bin=%d  Ranges from %d to %d", bin, (int)hranges[0], (int)hranges[1]);
	//putText(histImage, string, cvPoint(histImage.cols / 5, 30), cv::FONT_HERSHEY_PLAIN, (double)1.3, Scalar(255, 0, 0), 1, 8, 0);


	//imshow("直方图", histImage);
}


int ReadFruit(string names)
{
	Mat img = image_all;
	if (!img.data) {
		cout << "Miss Data" << endl;
		return -1;
	}
	resize(img, img, Size(), 0.5, 0.5);
	Mat img_cmyk, img_hsi;
	vector <Mat> vecRgb, vecHsi;
	split(img, vecRgb);
	img_hsi.create(img.rows, img.cols, CV_8UC3);
	rgb2hsi(img, img_hsi);
	split(img_hsi, vecHsi);
	//namedWindow("RGB_Image", CV_WINDOW_AUTOSIZE);
	//namedWindow("HSI_Image", CV_WINDOW_AUTOSIZE);
	//imshow("RGB_Image", img);
	//imshow("HSI_Image", img_hsi);
	int num_value=histogram(img_hsi,names);

	return num_value;
}

HBRUSH ConeDlg::OnCtlColor(CDC* pDC, CWnd* pWnd, UINT nCtlColor)
{
	HBRUSH hbr = CDialogEx::OnCtlColor(pDC, pWnd, nCtlColor);

	
	// TODO:  在此更改 DC 的任何特性
	return (HBRUSH)m_brush;
	// TODO:  如果默认的不是所需画笔，则返回另一个画笔
	//return hbr;
}


void ConeDlg::OnSize(UINT nType, int cx, int cy)
{
	CDialogEx::OnSize(nType, cx, cy);

	// TODO: 在此处添加消息处理程序代码
	// TODO:  在此处添加消息处理程序代码
	if (nType == SIZE_RESTORED || nType == SIZE_MAXIMIZED)//窗体大小发生变动。处理程序
	{
		float fsp[2];
		POINT Newp; //获取现在对话框的大小
		CRect recta;
		GetClientRect(&recta); //取客户区大小   
		Newp.x = recta.right - recta.left;
		Newp.y = recta.bottom - recta.top;
		fsp[0] = (float)Newp.x / Old.x;
		fsp[1] = (float)Newp.y / Old.y;
		CRect Rect;
		int woc;
		CPoint OldTLPoint, TLPoint; //左上角
		CPoint OldBRPoint, BRPoint; //右下角
		HWND hwndChild = ::GetWindow(m_hWnd, GW_CHILD); //列出所有控件   
		while (hwndChild)
		{
			woc = ::GetDlgCtrlID(hwndChild);//取得ID
			GetDlgItem(woc)->GetWindowRect(Rect);
			ScreenToClient(Rect);
			OldTLPoint = Rect.TopLeft();
			TLPoint.x = long(OldTLPoint.x*fsp[0]);
			TLPoint.y = long(OldTLPoint.y*fsp[1]);
			OldBRPoint = Rect.BottomRight();
			BRPoint.x = long(OldBRPoint.x *fsp[0]);
			BRPoint.y = long(OldBRPoint.y *fsp[1]); //高度不可读的控件（如:combBox),不要改变此值.
			Rect.SetRect(TLPoint, BRPoint);
			GetDlgItem(woc)->MoveWindow(Rect, TRUE);
			hwndChild = ::GetWindow(hwndChild, GW_HWNDNEXT);
		}
		Old = Newp;
	}

}


void ConeDlg::OnBnClickedButton44()
{
	// TODO: 在此添加控件通知处理程序代码

	photo mydlg;
	mydlg.DoModal();

}


void ConeDlg::OnEnChangekind002()
{
	// TODO:  如果该控件是 RICHEDIT 控件，它将不
	// 发送此通知，除非重写 CDialogEx::OnInitDialog()
	// 函数并调用 CRichEditCtrl().SetEventMask()，
	// 同时将 ENM_CHANGE 标志“或”运算到掩码中。

	// TODO:  在此添加控件通知处理程序代码
}




